package cn.com.connext.scrm.service;

import cn.com.connext.scrm.config.Constants;
import cn.com.connext.scrm.domain.master.ZnhjEntity;
import cn.com.connext.scrm.domain.master.ZnhjEntityTemp;
import cn.com.connext.scrm.repository.master.ZnhjEntityTempRepository;
import cn.com.connext.scrm.repository.master.ZnhjRepository;
import cn.com.connext.scrm.service.dto.AddProductResult;
import cn.com.connext.scrm.service.dto.JsonResult;
import cn.com.connext.scrm.service.dto.ZnhjAddDTO;
import cn.com.connext.scrm.service.dto.ZnhjOperation;
import cn.com.connext.scrm.service.mapper.ZnhjMapper;
import cn.com.connext.scrm.service.mapper.ZnhjService;
import cn.com.connext.scrm.web.rest.vm.IsScanVM;
import com.alibaba.fastjson.JSONObject;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang3.RandomUtils;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.jdbc.core.BatchPreparedStatementSetter;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.client.RestTemplate;

import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.text.SimpleDateFormat;
import java.time.ZonedDateTime;
import java.util.*;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.stream.Collectors;

@Service
@Transactional
public class ZnhjServiceImpl implements ZnhjService {
    private static final Logger logger = LoggerFactory.getLogger(ZnhjServiceImpl.class);

    @Autowired
    private ZnhjRepository znhjRepository;
    @Autowired
    private ZnhjMapper znhjMapper;

    @Autowired
    private JdbcTemplate template;//注入的方式

    @Autowired
    private ZnhjEntityTempRepository znhjEntityTempRepository;


    public Integer isActivate(String uniqueCode) {
        Integer count = znhjRepository.findIsActivate(uniqueCode);
        return count;
    }

    @Override
    public ZnhjEntity findByUniqueCodeAndBottomCode(String uniqueCode, String bottleCode) {
        return znhjRepository.findByUniqueCodeAndBottomCode(uniqueCode,bottleCode);
    }

    @Override
    @Transactional
    public AddProductResult addProducts(ZnhjOperation znhj){
        List<ZnhjAddDTO> receivelist = znhj.getList();
        AddProductResult result =new AddProductResult();
        if (CollectionUtils.isEmpty(receivelist)) {
            logger.info("第三方传输总数据为空");
            result.setCode(AddProductResult.ERROR);
            return result;
        }
        result.setCode(AddProductResult.SUCCESS);
        List<ZnhjEntityTemp> entities =new ArrayList<>();
        ZnhjEntityTemp entity = null;
        //记录批次号  需要返回
        String batchNo = "";
        try {
            logger.info("第三方传输总数据="+receivelist.size());
            List<ZnhjAddDTO> list = receivelist.stream().collect(
                Collectors.collectingAndThen(
                    Collectors.toCollection(() -> new TreeSet<>(Comparator.comparing(o->o.getBottleCode()+ ";" + o.getUniqueCode()))), ArrayList::new)
            );
            logger.info("第三方传输去重后总数据="+list.size());
            List<String> conditionList = new ArrayList<>();
            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
            for (int i =0;i<list.size();i++) {
                int count = i + 1;
                //记录批次号
                if (!StringUtils.isEmpty(list.get(i).getBatchNo()) && StringUtils.isEmpty(batchNo)) {
                    batchNo = list.get(i).getBatchNo();
                }
                logger.info("bottleCode:" + list.get(i).getBottleCode() + " --uniqueCode:" + list.get(i).getUniqueCode());
                entity = new ZnhjEntityTemp();
                BeanUtils.copyProperties(list.get(i),entity);
                String bottleUnique = entity.getBottleCode()+entity.getUniqueCode();
                entity.setBottleUnique(bottleUnique);
                if (StringUtils.isNotEmpty(list.get(i).getVoidTime())) {
                    entity.setVoidTime(sdf.parse(list.get(i).getVoidTime()));
                }
                if (StringUtils.isNotEmpty(list.get(i).getActiveTime())) {
                    entity.setActiveTime(sdf.parse(list.get(i).getActiveTime()));
                }
                entities.add(entity);
                conditionList.add(bottleUnique);
            }
            //todo 去除重复暂时不可考虑
       /* if(conditionList.size() >0){
            List<ZnhjEntity> all = znhjRepository.findByCondition(conditionList);
            entities.removeAll(all);
        }*/

            List<ZnhjEntityTemp> resultList =new ArrayList<>();
            if(entities.size() >0) {
                for (ZnhjEntityTemp entity1 : entities) {
                    entity1.setCreateTime(ZonedDateTime.now());
                    entity1.setStatus("00");
                    entity1.setOperation(znhj.getOperation());
                    resultList.add(entity1);
                }
            }
            ExecutorService executorService = Executors.newCachedThreadPool();
            final Future<AddProductResult> s = executorService.submit(new Callable<AddProductResult>() {
                @Override
                public AddProductResult call() throws Exception {
                    logger.info("执行异步操作：" + Thread.currentThread().getName());
                    znhjEntityTempRepository.save(resultList);
                    logger.info(Thread.currentThread().getName()+"异步线程执行完毕,本次共添加数据：" + resultList.size()+"条");
                    return  result;
                }
            });
            result.setNum(resultList.size());
            logger.info("数据总量="+resultList.size());
        } catch (Exception e) {
            logger.info("addProducts------------"+e.getMessage());
            result.setCode(AddProductResult.ERROR);
        }
        result.setBatchNo(batchNo);
        return  result;

    }
    //旧版一物一码代码
    /*public JsonResult addProducts(List<ZnhjAddDTO> receivelist){
        JsonResult jsonResult =new JsonResult();
        List<ZnhjEntity> entities =new ArrayList<>();
        ZnhjEntity entity = null;
        logger.info("第三方传输总数据="+receivelist.size());
        List<ZnhjAddDTO> list = receivelist.stream().collect(
            Collectors.collectingAndThen(
                Collectors.toCollection(() -> new TreeSet<>(Comparator.comparing(o->o.getBottleCode()+ ";" + o.getUniqueCode()))), ArrayList::new)
        );
        logger.info("第三方传输去重后总数据="+list.size());
        List<String> conditionList = new ArrayList<>();
        for (int i =0;i<list.size();i++) {
            int count = i + 1;
            if (StringUtils.isEmpty(list.get(i).getBottleCode())) {
                jsonResult.setState(1);
                jsonResult.setMessage("瓶码不能为空!第" + count + "条数据瓶码为空");
                return jsonResult;
            } else if (StringUtils.isEmpty(list.get(i).getSkuId())) {
                jsonResult.setState(1);
                jsonResult.setMessage("skuId不能为空!第" + count + "条数据skuId为空");
                return jsonResult;
            } else if (StringUtils.isEmpty(list.get(i).getUniqueCode())) {
                jsonResult.setState(1);
                jsonResult.setMessage("提交码不能为空!第" + count + "条数据提交码为空");
                return jsonResult;
            }
            logger.info("bottleCode:" + list.get(i).getBottleCode() + " --uniqueCode:" + list.get(i).getUniqueCode());
            entity = new ZnhjEntity();
            BeanUtils.copyProperties(list.get(i),entity);
//            String s = genCodes(6);
            String bottleUnique = entity.getBottleCode()+entity.getUniqueCode();
            entity.setBottleUnique(bottleUnique);
            entities.add(entity);
            conditionList.add(bottleUnique);
        }
        if(conditionList.size() >0){
            List<ZnhjEntity> all = znhjRepository.findByCondition(conditionList);
            entities.removeAll(all);
        }

        List<ZnhjEntity> resultList =new ArrayList<>();
        if(entities.size() >0) {
            for (ZnhjEntity entity1 : entities) {
                entity1.setCreateTime(ZonedDateTime.now());
                entity1.setIsActivity(2);
                entity1.setStatus(1);
                entity1.setIsScan(2);//是否被扫描 1是 2否
                resultList.add(entity1);
            }
        }
        ExecutorService executorService = Executors.newCachedThreadPool();
        final Future<JsonResult> s = executorService.submit(new Callable<JsonResult>() {
            @Override
            public JsonResult call() throws Exception {
                logger.info("执行异步操作：" + Thread.currentThread().getName());
                znhjRepository.save(resultList);
                jsonResult.setState(0);
                jsonResult.setMessage(Thread.currentThread().getName()+"异步线程执行完毕,本次共添加数据"+resultList.size()+"条");
                logger.info(Thread.currentThread().getName()+"异步线程执行完毕,本次共添加数据：" + resultList.size()+"条");
                return  jsonResult;
            }
        });
        logger.info("数据总量="+resultList.size());
        jsonResult.setState(0);
        jsonResult.setMessage("添加成功,本次共添加数据"+resultList.size()+"条");
        return  jsonResult;

    }*/


    public JsonResult deleteProducts(List<ZnhjAddDTO> list) {
        JsonResult jsonResult =new JsonResult();
        Collection<String> collection = new ArrayList<>();
        if(list !=null && list.size() >0) {
            for (int i = 0; i < list.size(); i++) {
                collection.add(list.get(i).getBottleCode());
            }
        }
        if(collection.size() >0){
            znhjRepository.batchUpdate(collection);
        }
        logger.info("退货成功,本次共退货"+list.size()+"条");
        jsonResult.setState(0);
        jsonResult.setMessage("退货成功,本次共退货"+list.size()+"条");
        return  jsonResult;
    }

    @Override
    public JsonResult updateIsScan(IsScanVM vm) {
        JsonResult result = new JsonResult();
        if(StringUtils.isEmpty(vm.getBottomCode()) || StringUtils.isEmpty(vm.getSkuId())){
                result.setState(-1);
                result.setMessage("skuId不能为空！");
        }else{
            znhjRepository.updateIsScan(vm.getBottomCode(),vm.getSkuId());
            result.setState(0);
            result.setMessage("瓶码被扫描成功");
        }
        return result;
    }

    @Override
    public JsonResult findSkuByBottleCode(ZnhjEntity entity) {
        JsonResult result = new JsonResult();
        if(StringUtils.isEmpty(entity.getBottleCode())){
            result.setState(-1);
            result.setMessage("参数瓶码不能为空！");
        }else{
            ZnhjEntity znhj = znhjRepository.findByBottleCode(entity.getBottleCode());
            result.setData(znhj);
            result.setState(0);
            result.setMessage("瓶码被扫描成功");
        }
        return result;
    }



        public static String genCodes(int length){

                String val = "";

                Random random = new Random();
                for(int i = 0; i < length; i++)
                {
                    String charOrNum = random.nextInt(2) % 2 == 0 ? "char" : "num"; // 输出字母还是数字

                    if("char".equalsIgnoreCase(charOrNum)) // 字符串
                    {
                        int choice = random.nextInt(2) % 2 == 0 ? 65 : 97; //取得大写字母还是小写字母
                        val += (char) (choice + random.nextInt(26));
                    }
                    else if("num".equalsIgnoreCase(charOrNum)) // 数字
                    {
                        val += String.valueOf(random.nextInt(10));
                    }
                }
                val=val.toLowerCase();

            return val;

        }

        @Override
        public JSONObject getNumByReelCode(String reelCode) {
            JSONObject jsonObj = new JSONObject();
            jsonObj.put("reelCode",reelCode);
            RestTemplate restTemplate=new RestTemplate();
            String requestUrl = Constants.GET_NUM_BY_REEL_CODE;
            HttpHeaders headers = new HttpHeaders();
            MediaType type = MediaType.parseMediaType("application/json; charset=UTF-8");
            headers.setContentType(type);
            headers.add("Accept", MediaType.APPLICATION_JSON.toString());
            HttpEntity<String> formEntity = new HttpEntity<String>(jsonObj.toString(), headers);
            JSONObject result=restTemplate.postForEntity(requestUrl,formEntity,JSONObject.class).getBody();
            return result;
        }

    }
